// Package service internal/service/admin_service.go
package service

import (
	"github.com/gin-gonic/gin"
	"github.com/go-playground/validator/v10"
	"github.com/jinzhu/copier"
	"gozrd-admin-api/internal/entity/dto"
	"gozrd-admin-api/internal/entity/model"
	"gozrd-admin-api/internal/entity/query"
	"gozrd-admin-api/internal/entity/vo"
	"gozrd-admin-api/internal/repository"
	"gozrd-admin-api/pkg/response"
	"time"
)

// IAdminService 管理员服务接口
type IAdminService interface {
	CreateSysAdmin(c *gin.Context, dto dto.AddSysAdminDto)
	GetSysAdmin(c *gin.Context, id int)
	UpdateSysAdmin(c *gin.Context, dto dto.UpdateSysAdminDto)
	DeleteSysAdmin(c *gin.Context, id int)
	UpdateSysAdminStatus(c *gin.Context, dto dto.UpdateSysAdminStatusDto)
	ResetSysAdminPassword(c *gin.Context, resetDTO dto.ResetSysAdminPasswordDto)
	UpdatePersonal(c *gin.Context, personalDTO dto.UpdatePersonalDto)
	UpdatePersonalPassword(c *gin.Context, passwordDTO dto.UpdatePersonalPasswordDto)
	GetSysAdminList(c *gin.Context, pageSize, pageNum int, username, status, beginTime, endTime string)
}

// AdminServiceImpl 管理员服务实现
type AdminServiceImpl struct {
	adminRepository repository.IAdminRepository
	validator       *validator.Validate
}

// NewAdminService 创建管理员服务实例
func NewAdminService(adminRepo repository.IAdminRepository) IAdminService {
	return &AdminServiceImpl{
		adminRepository: adminRepo,
		validator:       validator.New(),
	}
}

// CreateSysAdmin 创建管理员
func (s *AdminServiceImpl) CreateSysAdmin(c *gin.Context, adminDTO dto.AddSysAdminDto) {
	// 验证DTO
	if err := s.validator.Struct(adminDTO); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		return
	}

	// 检查用户是否已存在
	existingAdmin, _ := s.adminRepository.GetSysAdminByUsername(adminDTO.Username)
	if existingAdmin.ID > 0 {
		response.Fail(c, response.BadRequest, "用户名已存在")
		return
	}

	// DTO转换为领域模型
	var admin model.SysAdmin
	if err := copier.Copy(&admin, &adminDTO); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		// response.FailWithCode(c, response.ErrServer, "数据转换失败")
		return
	}

	// 补充领域模型中的其他字段
	admin.CreateTime = time.Now()

	// 调用Repository
	err := s.adminRepository.CreateSysAdmin(adminDTO.RoleId, admin)
	if err != nil {

		response.Fail(c, response.ErrDatabase, "创建用户失败："+err.Error())
		return
	}

	response.SuccessWithMessage(c, "ok", nil)
}

// GetSysAdmin 通过id获取管理员
func (s *AdminServiceImpl) GetSysAdmin(c *gin.Context, id int) {
	AdminVo, err := s.adminRepository.GetSysAdminInfo(id)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "通过id获取管理员错误"+err.Error())
		return
	}
	response.Success(c, AdminVo)
}

// UpdateSysAdmin 修改用户
func (s *AdminServiceImpl) UpdateSysAdmin(c *gin.Context, adminDTO dto.UpdateSysAdminDto) {
	// 验证DTO
	if err := s.validator.Struct(adminDTO); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		return
	}

	// DTO转换为领域模型
	var admin model.SysAdmin
	if err := copier.Copy(&admin, &adminDTO); err != nil {
		response.Fail(c, response.ErrParams, "数据转换失败: "+err.Error())
		return
	}

	// 调用Repository层
	updatedAdmin, err := s.adminRepository.UpdateSysAdmin(admin, adminDTO.RoleId)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "更新用户失败："+err.Error())
		return
	}

	response.Success(c, updatedAdmin)
}

// DeleteSysAdmin 通过 id 删除用户
func (s *AdminServiceImpl) DeleteSysAdmin(c *gin.Context, id int) {
	if err := s.adminRepository.DeleteSysAdminById(id); err != nil {
		response.Fail(c, response.ErrDatabase, "删除用户失败："+err.Error())
		return
	}
	response.Success(c, nil)
}

// UpdateSysAdminStatus 更新用户状态
func (s *AdminServiceImpl) UpdateSysAdminStatus(c *gin.Context, dto dto.UpdateSysAdminStatusDto) {
	// 验证DTO
	if err := s.validator.Struct(dto); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		return
	}

	// 调用Repository层，不透传DTO
	err := s.adminRepository.UpdateSysAdminStatus(dto.Id, dto.Status)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "更新用户状态失败："+err.Error())
		return
	}

	response.Success(c, nil)
}

// ResetSysAdminPassword 重置密码, 管理员修改用户密码
func (s *AdminServiceImpl) ResetSysAdminPassword(c *gin.Context, resetDTO dto.ResetSysAdminPasswordDto) {
	// 验证DTO
	if err := s.validator.Struct(resetDTO); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		return
	}

	// 调用Repository层，不透传DTO
	err := s.adminRepository.ResetSysAdminPassword(resetDTO.Id, resetDTO.Password)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "管理员修改用户密码失败："+err.Error())
		return
	}

	response.Success(c, nil)
}

// UpdatePersonal 更新用户信息
func (s *AdminServiceImpl) UpdatePersonal(c *gin.Context, personalDTO dto.UpdatePersonalDto) {
	// 验证DTO
	if err := s.validator.Struct(personalDTO); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		return
	}

	// DTO转换为领域模型
	var admin model.SysAdmin
	//admin.ID = personalDTO.Id
	//admin.Icon = personalDTO.Icon
	//admin.Username = personalDTO.Username
	//admin.Nickname = personalDTO.Nickname
	//admin.Phone = personalDTO.Phone
	//admin.Email = personalDTO.Email
	//admin.Note = personalDTO.Note

	// 也可以使用copier库
	if err := copier.Copy(&admin, &personalDTO); err != nil {
		response.Fail(c, response.ErrParams, "数据转换失败: "+err.Error())
		return
	}

	// 调用Repository层，传递领域模型而非DTO
	updatedAdmin, err := s.adminRepository.UpdatePersonal(admin)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "更新用户信息失败："+err.Error())
		return
	}

	response.Success(c, updatedAdmin)
}

// UpdatePersonalPassword 更改个人密码 todo 加密密码
func (s *AdminServiceImpl) UpdatePersonalPassword(c *gin.Context, passwordDTO dto.UpdatePersonalPasswordDto) {
	// 验证DTO
	if err := s.validator.Struct(passwordDTO); err != nil {
		response.Fail(c, response.ErrParams, err.Error())
		return
	}

	// 验证新密码与重复密码是否一致
	if passwordDTO.NewPassword != passwordDTO.ResetPassword {
		response.Fail(c, response.ErrParams, "新密码与重复密码不一致")
		return
	}

	// 获取当前用户信息，验证原密码是否正确
	currentAdmin, err := s.adminRepository.GetSysAdminById(passwordDTO.Id)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "获取用户信息失败："+err.Error())
		return
	}

	// 验证原密码是否正确（这里假设密码已加密，实际使用时需要根据加密方式处理） todo
	if currentAdmin.Password != passwordDTO.Password {
		response.Fail(c, response.BadRequest, "原密码不正确")
		return
	}

	// 调用Repository层，不透传DTO
	admin, err := s.adminRepository.UpdatePersonalPassword(passwordDTO.Id, passwordDTO.NewPassword)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "更改个人密码失败："+err.Error())
		return
	}

	response.Success(c, admin)
}

// GetSysAdminList 改进后的服务层方法
func (s *AdminServiceImpl) GetSysAdminList(c *gin.Context, pageSize, pageNum int, username, status, beginTime, endTime string) {
	// 验证分页参数
	if pageNum <= 0 {
		pageNum = 1
	}
	if pageSize <= 0 || pageSize > 100 {
		pageSize = 10
	}

	// 创建查询参数
	queryParams := query.SysAdminQuery{
		PageNum:   pageNum,
		PageSize:  pageSize,
		Username:  username,
		Status:    status,
		BeginTime: beginTime,
		EndTime:   endTime,
	}

	// 调用Repository层
	result, err := s.adminRepository.GetSysAdminList(queryParams)
	if err != nil {
		response.Fail(c, response.ErrDatabase, "获取管理员列表失败："+err.Error())
		return
	}

	// 转换为VO
	adminVoList := make([]vo.SysAdminVo, 0, len(result.Admins))
	for _, admin := range result.Admins {
		roleId := result.RoleMapping[admin.ID]

		adminVo := vo.SysAdminVo{
			ID:         admin.ID,
			Username:   admin.Username,
			Nickname:   admin.Nickname,
			Status:     admin.Status,
			PostId:     admin.PostId,
			PostName:   result.PostNames[admin.PostId],
			DeptId:     admin.DeptId,
			DeptName:   result.DeptNames[admin.DeptId],
			RoleId:     roleId,
			RoleName:   result.RoleNames[roleId],
			Email:      admin.Email,
			Phone:      admin.Phone,
			Note:       admin.Note,
			CreateTime: admin.CreateTime,
		}
		adminVoList = append(adminVoList, adminVo)
	}

	// 构建结果
	voResult := vo.SysAdminListVo{
		Total: result.Total,
		List:  adminVoList,
	}

	response.Success(c, voResult)
}
